#include "head.h"


CircularQueue::CircularQueue()
    :_product(0)
    ,_consume(0)
{
//    for(auto i = 0;i < _arr.size();i++)
//    {
//        Unity temp;

//        _arr[i] =
//    }
//    AVPacket temp;
//    _arr.fill(temp);
}

//该析构函数不保证线程安全
void CircularQueue::Destroy()
{
    while (_product != _consume) {
        av_packet_unref(&_arr[_consume]._apk);

        ++_consume;
        if(!(_consume % _arr.size()))
        {
            _consume = 0;
        }
    }
}


CircularQueue::~CircularQueue()
{
    Destroy();
}

//只是读而已，而且不需要很准确的实时数据，无需加锁
int CircularQueue::GetCurSize()
{
    if(_product == _consume)
    {
        return 0;
    }
    if(_product + 1 == _consume || (_product + 1)%static_cast<int>(_arr.size()) == _consume)
    {
        return _arr.size() - 1;
    }
    if(_product < _consume)
    {
        auto size = _arr.size() - _consume + 1;
        size += _product - 1;
        return  size;
    }
    if(_product > _consume)
    {
        return  _product - _consume;
    }
    return  -1;
}


//要事先判断空与满。
void CircularQueue::AddElement(AVPacket *ele)
{
    std::lock_guard<std::mutex> lock(_arr[_product]._mutex);
    av_packet_ref(&_arr[_product]._apk, ele);
    ++_product;
//    std::cout << "AddElement" << std::endl;;
    if(!(_product % _arr.size()))
    {
        _product = 0;
    }


}

//要事先判断空与满。
void CircularQueue::Consume(AVPacket *ele)
{
    std::lock_guard<std::mutex> lock(_arr[_consume]._mutex);
    av_packet_ref(ele, &_arr[_consume]._apk);
    av_packet_unref(&_arr[_consume]._apk);
//    _arr[_consume] = nullptr;
    ++_consume;
//    std::cout << "Consume" << std::endl;
    if(!(_consume % _arr.size()))
    {
        _consume = 0;
    }
}
